<template><div><h2 id="_1-前言" tabindex="-1"><a class="header-anchor" href="#_1-前言" aria-hidden="true">#</a> 1. 前言</h2>
<p>计划使用<code v-pre>Vupress2.X</code>加上<code v-pre>Element-plus</code>实现封装的组件库说明。</p>
<h2 id="_2-vuepress项目初始化" tabindex="-1"><a class="header-anchor" href="#_2-vuepress项目初始化" aria-hidden="true">#</a> 2. Vuepress项目初始化</h2>
<h2 id="_2-1-准备工作" tabindex="-1"><a class="header-anchor" href="#_2-1-准备工作" aria-hidden="true">#</a> 2.1 准备工作</h2>
<p>新建一个<code v-pre>Vuepress2.X</code>项目文件夹，命名为<code v-pre>VuepressTest</code>，并下载依赖：</p>
<div class="language-typescript ext-ts line-numbers-mode"><pre v-pre class="language-typescript"><code>npm install <span class="token operator">-</span><span class="token constant">D</span> vuepress<span class="token decorator"><span class="token at operator">@</span><span class="token function">next</span></span>
npm install
</code></pre><div class="line-numbers" aria-hidden="true"><div class="line-number"></div><div class="line-number"></div></div></div><h2 id="_2-2-配置" tabindex="-1"><a class="header-anchor" href="#_2-2-配置" aria-hidden="true">#</a> 2.2 配置</h2>
<p>在<code v-pre>package.json</code>中添加<code v-pre>scripts</code>：</p>
<div class="language-tsx ext-tsx line-numbers-mode"><pre v-pre class="language-tsx"><code><span class="token punctuation">{</span>
  <span class="token string-property property">"scripts"</span><span class="token operator">:</span> <span class="token punctuation">{</span>
    <span class="token string-property property">"dev"</span><span class="token operator">:</span> <span class="token string">"vuepress dev docs"</span><span class="token punctuation">,</span>
    <span class="token string-property property">"build"</span><span class="token operator">:</span> <span class="token string">"vuepress build docs"</span>
  <span class="token punctuation">}</span>
<span class="token punctuation">}</span>
</code></pre><div class="line-numbers" aria-hidden="true"><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div></div></div><h2 id="_2-3-示例" tabindex="-1"><a class="header-anchor" href="#_2-3-示例" aria-hidden="true">#</a> 2.3 示例</h2>
<p>在<code v-pre>VuepressTest</code>项目中新建<code v-pre>doc/README.md</code>，并写下如下内容：</p>
<div class="language-markdown ext-md line-numbers-mode"><pre v-pre class="language-markdown"><code><span class="token front-matter-block"><span class="token punctuation">---</span>
<span class="token front-matter yaml language-yaml"><span class="token key atrule">home</span><span class="token punctuation">:</span> <span class="token boolean important">true</span>
<span class="token key atrule">heroImage</span><span class="token punctuation">:</span> https<span class="token punctuation">:</span>//artice<span class="token punctuation">-</span>code<span class="token punctuation">-</span>1258339218.cos.ap<span class="token punctuation">-</span>beijing.myqcloud.com/vuepress/element<span class="token punctuation">-</span>index.png
<span class="token key atrule">heroText</span><span class="token punctuation">:</span> Element
<span class="token key atrule">features</span><span class="token punctuation">:</span>
<span class="token punctuation">-</span> <span class="token key atrule">title</span><span class="token punctuation">:</span> 一致性 Consistency
  <span class="token key atrule">details</span><span class="token punctuation">:</span> 与现实生活一致：与现实生活的流程、逻辑保持一致，遵循用户习惯的语言和概念
<span class="token punctuation">-</span> <span class="token key atrule">title</span><span class="token punctuation">:</span> 反馈 Feedback
  <span class="token key atrule">details</span><span class="token punctuation">:</span> 通过界面样式和交互动效让用户可以清晰的感知自己的操作
<span class="token punctuation">-</span> <span class="token key atrule">title</span><span class="token punctuation">:</span> 效率 Efficiency
  <span class="token key atrule">details</span><span class="token punctuation">:</span> 界面简单直白，让用户快速识别而非回忆，减少用户记忆负担。
<span class="token key atrule">footer</span><span class="token punctuation">:</span> by饿了么</span>
<span class="token punctuation">---</span></span>
</code></pre><div class="line-numbers" aria-hidden="true"><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div></div></div><p>运行<code v-pre>npm run dev</code>之后，效果如下所示：</p>
<img src="@source/vue/2021/1222/image004.png" style="zoom:50%;" />
<h1 id="_3-使用element-plus" tabindex="-1"><a class="header-anchor" href="#_3-使用element-plus" aria-hidden="true">#</a> 3. 使用Element-Plus</h1>
<h2 id="_3-1-安装" tabindex="-1"><a class="header-anchor" href="#_3-1-安装" aria-hidden="true">#</a> 3.1 安装</h2>
<div class="language-tsx ext-tsx line-numbers-mode"><pre v-pre class="language-tsx"><code>npm install element<span class="token operator">-</span>plus <span class="token operator">--</span>save
</code></pre><div class="line-numbers" aria-hidden="true"><div class="line-number"></div></div></div><h2 id="_3-2-配置" tabindex="-1"><a class="header-anchor" href="#_3-2-配置" aria-hidden="true">#</a> 3.2 配置</h2>
<p>在<code v-pre>.vuepress</code>中新建文件<code v-pre>clientAppEnhance.ts</code>，引入<code v-pre>element-plus</code>：</p>
<div class="language-tsx ext-tsx line-numbers-mode"><pre v-pre class="language-tsx"><code><span class="token keyword">import</span> <span class="token punctuation">{</span> defineClientAppEnhance <span class="token punctuation">}</span> <span class="token keyword">from</span> <span class="token string">'@vuepress/client'</span>
<span class="token keyword">import</span> ElementPlus <span class="token keyword">from</span> <span class="token string">'element-plus'</span>
<span class="token keyword">import</span> <span class="token string">'element-plus/dist/index.css'</span>

<span class="token keyword">export</span> <span class="token keyword">default</span> <span class="token function">defineClientAppEnhance</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token punctuation">{</span> app<span class="token punctuation">,</span> router<span class="token punctuation">,</span> siteData <span class="token punctuation">}</span><span class="token punctuation">)</span> <span class="token operator">=></span> <span class="token punctuation">{</span>
    app<span class="token punctuation">.</span><span class="token function">use</span><span class="token punctuation">(</span>ElementPlus<span class="token punctuation">)</span>
<span class="token punctuation">}</span><span class="token punctuation">)</span>
</code></pre><div class="line-numbers" aria-hidden="true"><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div></div></div><h2 id="_3-3-示例" tabindex="-1"><a class="header-anchor" href="#_3-3-示例" aria-hidden="true">#</a> 3.3 示例</h2>
<p>在<code v-pre>VuepressTest</code>项目中新建<code v-pre>doc/README.md</code>，并写下如下内容：</p>
<div class="language-tsx ext-tsx line-numbers-mode"><pre v-pre class="language-tsx"><code><span class="token operator">--</span><span class="token operator">-</span>
home<span class="token operator">:</span> <span class="token boolean">true</span>
<span class="token operator">--</span><span class="token operator">-</span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>el-button</span> <span class="token attr-name">type</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">"</span>primary<span class="token punctuation">"</span></span> <span class="token attr-name">:icon</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">"</span>Edit<span class="token punctuation">"</span></span><span class="token punctuation">></span></span><span class="token plain-text">我是Element-Plus</span><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>el-button</span><span class="token punctuation">></span></span>
</code></pre><div class="line-numbers" aria-hidden="true"><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div></div></div><p>效果如下所示：</p>
<img src="@source/vue/2021/1222/image005.png" style="zoom:50%;" />
<h2 id="_3-4-webpack下出现-mjs相关报错" tabindex="-1"><a class="header-anchor" href="#_3-4-webpack下出现-mjs相关报错" aria-hidden="true">#</a> 3.4 Webpack下出现.mjs相关报错</h2>
<p>当前打包使用<code v-pre>Vite</code>，项目正常启动，如果是<code v-pre>Webpack</code>打包，运行<code v-pre>npm run dev</code>，可能会出现与<code v-pre>Element-Plus</code>相关的报错信息，如下所示：</p>
<img src="@source/vue/2021/1222/image001.png" style="zoom:50%;" />
<div class="language-tsx ext-tsx line-numbers-mode"><pre v-pre class="language-tsx"><code><span class="token punctuation">(</span>probably because the origin <span class="token keyword">is</span> strict EcmaScript Module<span class="token punctuation">,</span> e<span class="token punctuation">.</span> g<span class="token punctuation">.</span> a <span class="token keyword">module</span> <span class="token keyword">with</span> javascript mimetype<span class="token punctuation">,</span> a <span class="token string">'*. mjs'</span> file<span class="token punctuation">,</span> or a <span class="token string">'*.js'</span> file where the <span class="token keyword">package</span><span class="token punctuation">.</span> json contains <span class="token string">'"type": "module"'</span><span class="token punctuation">)</span><span class="token punctuation">.</span> 
The extension <span class="token keyword">in</span> the request <span class="token keyword">is</span> mandatory <span class="token keyword">for</span> it to be fully specified<span class="token punctuation">.</span> 
Add the extension to the request<span class="token punctuation">.</span>
</code></pre><div class="line-numbers" aria-hidden="true"><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div></div></div><p>我们可以看下<a href="https://webpack.docschina.org/api/module-methods/" target="_blank" rel="noopener noreferrer">Webpack官方文档<ExternalLinkIcon/></a>官方文档中对这方面的解释，如下所示：</p>
<img src="@source/vue/2021/1222/image002.png" style="zoom:50%;" />
<p>如果要去掉这个限制，只需要设置<code v-pre>Rule.resolve.fullySpecified</code>为<code v-pre>false</code>即可，具体看如下所示：</p>
<img src="@source/vue/2021/1222/image003.png" alt="image003" style="zoom:50%;" />
<p>所以，我们需要在<code v-pre>config.ts</code>中进行设置，这样就没有问题了，如下所示：</p>
<div class="language-tsx ext-tsx line-numbers-mode"><pre v-pre class="language-tsx"><code><span class="token keyword">import</span> <span class="token punctuation">{</span> defineUserConfig <span class="token punctuation">}</span> <span class="token keyword">from</span> <span class="token string">'vuepress'</span>
<span class="token keyword">import</span> <span class="token keyword">type</span> <span class="token punctuation">{</span> DefaultThemeOptions <span class="token punctuation">}</span> <span class="token keyword">from</span> <span class="token string">'vuepress'</span>
<span class="token keyword">export</span> <span class="token keyword">default</span> <span class="token generic-function"><span class="token function">defineUserConfig</span><span class="token generic class-name"><span class="token operator">&lt;</span>DefaultThemeOptions<span class="token operator">></span></span></span><span class="token punctuation">(</span><span class="token punctuation">{</span>
  bundlerConfig<span class="token operator">:</span> <span class="token punctuation">{</span>
    <span class="token comment">// 可以看Vuepress 2.X官方文档相关chainWebpack的信息，如果报错，需依赖webpack-chain</span>
    <span class="token function-variable function">chainWebpack</span><span class="token operator">:</span> <span class="token punctuation">(</span>config<span class="token punctuation">,</span> isServer<span class="token punctuation">,</span> isBuild<span class="token punctuation">)</span> <span class="token operator">=></span> <span class="token punctuation">{</span>
      config<span class="token punctuation">.</span>module
        <span class="token punctuation">.</span><span class="token function">rule</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
        <span class="token punctuation">.</span><span class="token function">test</span><span class="token punctuation">(</span><span class="token regex"><span class="token regex-delimiter">/</span><span class="token regex-source language-regex">\.m?jsx?$</span><span class="token regex-delimiter">/</span></span><span class="token punctuation">)</span>
        <span class="token punctuation">.</span>resolve<span class="token punctuation">.</span><span class="token function">set</span><span class="token punctuation">(</span><span class="token string">'fullySpecified'</span><span class="token punctuation">,</span> <span class="token boolean">false</span><span class="token punctuation">)</span>
    <span class="token punctuation">}</span>

  <span class="token punctuation">}</span>
<span class="token punctuation">}</span><span class="token punctuation">)</span>
</code></pre><div class="line-numbers" aria-hidden="true"><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div></div></div><h2 id="_3-5-element-plus组件显示图标" tabindex="-1"><a class="header-anchor" href="#_3-5-element-plus组件显示图标" aria-hidden="true">#</a> 3.5 Element-Plus组件显示图标</h2>
<p>可以发现，在上面的按钮示例中，图标设置<code v-pre>:icon=&quot;Edit&quot;</code>并没有生效，原因是Element-Plus的图标需自己引入。</p>
<p>首先，需安装依赖，如下所示：</p>
<div class="language-tsx ext-tsx line-numbers-mode"><pre v-pre class="language-tsx"><code>npm install <span class="token decorator"><span class="token at operator">@</span><span class="token function">element</span></span><span class="token operator">-</span>plus<span class="token operator">/</span>icons<span class="token operator">-</span>vue
</code></pre><div class="line-numbers" aria-hidden="true"><div class="line-number"></div></div></div><p>然后在<code v-pre>clientAppEnhance.ts</code>中引入<code v-pre>icon-vue</code>，如下所示：</p>
<div class="language-tsx ext-tsx line-numbers-mode"><pre v-pre class="language-tsx"><code><span class="token keyword">import</span> <span class="token operator">*</span> <span class="token keyword">as</span> ElIcons <span class="token keyword">from</span> <span class="token string">'@element-plus/icons-vue'</span>

<span class="token keyword">export</span> <span class="token keyword">default</span> <span class="token function">defineClientAppEnhance</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token punctuation">{</span> app<span class="token punctuation">,</span> router<span class="token punctuation">,</span> siteData <span class="token punctuation">}</span><span class="token punctuation">)</span> <span class="token operator">=></span> <span class="token punctuation">{</span>
    
   	<span class="token operator">...</span><span class="token operator">...</span>
    
    Object<span class="token punctuation">.</span><span class="token function">keys</span><span class="token punctuation">(</span>ElIcons<span class="token punctuation">)</span><span class="token punctuation">.</span><span class="token function">forEach</span><span class="token punctuation">(</span>key <span class="token operator">=></span> <span class="token punctuation">{</span>
        app<span class="token punctuation">.</span><span class="token function">component</span><span class="token punctuation">(</span>key<span class="token punctuation">,</span> ElIcons<span class="token punctuation">[</span>key<span class="token punctuation">]</span><span class="token punctuation">)</span>
    <span class="token punctuation">}</span><span class="token punctuation">)</span>
    
<span class="token punctuation">}</span><span class="token punctuation">)</span>
</code></pre><div class="line-numbers" aria-hidden="true"><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div></div></div><p>这样就可以让<code v-pre>Element-Plus</code>组件显示图标了，效果如下所示：</p>
<img src="@source/vue/2021/1222/image006.png" style="zoom:50%;" />
<h1 id="_4-markdown中使用vue" tabindex="-1"><a class="header-anchor" href="#_4-markdown中使用vue" aria-hidden="true">#</a> 4. Markdown中使用Vue</h1>
<p>如果要对自己封装的组件进行说明，最想要的效果，当然是类似<code v-pre>Element-plus</code>文档那样，能够有组件示例，然后有个切换查看源码的功能，所以就很想知道能不能在<code v-pre>.MD</code>文件中使用<code v-pre>Vue</code>，其实<code v-pre>Vuepress</code>已经提供了该功能，直接使用在<code v-pre>.MD</code>中编写代码即可。</p>
<p>这种方式只适合简单的代码示例，复杂逻辑的最好还是以组件方式在<code v-pre>.MD</code>文件中引入。</p>
<h2 id="_4-1-自定义组件" tabindex="-1"><a class="header-anchor" href="#_4-1-自定义组件" aria-hidden="true">#</a> 4.1 自定义组件</h2>
<p>首先需在<code v-pre>.vuepress</code>中新建<code v-pre>components</code>文件夹，然后新建<code v-pre>Test.vue</code>文件，内容如下所示：</p>
<div class="language-tsx ext-tsx line-numbers-mode"><pre v-pre class="language-tsx"><code><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>template</span><span class="token punctuation">></span></span><span class="token plain-text">
    </span><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>h1</span><span class="token punctuation">></span></span><span class="token plain-text">在README.md中引入Test.vue组件文件</span><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>h1</span><span class="token punctuation">></span></span><span class="token plain-text">
</span><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>template</span><span class="token punctuation">></span></span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>script</span> <span class="token attr-name">lang</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">"</span>ts<span class="token punctuation">"</span></span><span class="token punctuation">></span></span><span class="token plain-text">
import { defineComponent } from 'vue'
export default defineComponent({
    setup() {},
})
</span><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>script</span><span class="token punctuation">></span></span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>style</span> <span class="token attr-name">lang</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">"</span>less<span class="token punctuation">"</span></span> <span class="token attr-name">scoped</span><span class="token punctuation">></span></span><span class="token plain-text">

</span><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>style</span><span class="token punctuation">></span></span>

</code></pre><div class="line-numbers" aria-hidden="true"><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div></div></div><h2 id="_4-2-自动注册vue组件" tabindex="-1"><a class="header-anchor" href="#_4-2-自动注册vue组件" aria-hidden="true">#</a> 4.2 自动注册Vue组件</h2>
<ol>
<li>使用Vuepress的插件<code v-pre>@vuepress/plugin-register-components</code>，用于根据组件文件或目录自动注册 Vue 组件。</li>
</ol>
<div class="language-tsx ext-tsx line-numbers-mode"><pre v-pre class="language-tsx"><code>npm i <span class="token operator">-</span><span class="token constant">D</span> <span class="token decorator"><span class="token at operator">@</span><span class="token function">vuepress</span></span><span class="token operator">/</span>plugin<span class="token operator">-</span>register<span class="token operator">-</span>components<span class="token decorator"><span class="token at operator">@</span><span class="token function">next</span></span>
</code></pre><div class="line-numbers" aria-hidden="true"><div class="line-number"></div></div></div><ol start="2">
<li>在<code v-pre>config.ts</code>中设置，如下所示：</li>
</ol>
<div class="language-tsx ext-tsx line-numbers-mode"><pre v-pre class="language-tsx"><code><span class="token keyword">import</span> <span class="token punctuation">{</span> path <span class="token punctuation">}</span> <span class="token keyword">from</span> <span class="token string">'@vuepress/utils'</span>

<span class="token keyword">export</span> <span class="token keyword">default</span> <span class="token generic-function"><span class="token function">defineUserConfig</span><span class="token generic class-name"><span class="token operator">&lt;</span>DefaultThemeOptions<span class="token operator">></span></span></span><span class="token punctuation">(</span><span class="token punctuation">{</span>
    
  <span class="token operator">...</span><span class="token operator">...</span>
    
  plugins<span class="token operator">:</span> <span class="token punctuation">[</span>
    <span class="token punctuation">[</span>
      <span class="token string">'@vuepress/register-components'</span><span class="token punctuation">,</span>
      <span class="token punctuation">{</span>
        componentsDir<span class="token operator">:</span> path<span class="token punctuation">.</span><span class="token function">resolve</span><span class="token punctuation">(</span>__dirname<span class="token punctuation">,</span> <span class="token string">'./components'</span><span class="token punctuation">)</span><span class="token punctuation">,</span>
      <span class="token punctuation">}</span><span class="token punctuation">,</span>
    <span class="token punctuation">]</span><span class="token punctuation">,</span>
  <span class="token punctuation">]</span><span class="token punctuation">,</span>
<span class="token punctuation">}</span><span class="token punctuation">)</span>
</code></pre><div class="line-numbers" aria-hidden="true"><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div></div></div><h2 id="_4-3-基本使用" tabindex="-1"><a class="header-anchor" href="#_4-3-基本使用" aria-hidden="true">#</a> 4.3 基本使用</h2>
<ol>
<li>这样就可以在<code v-pre>.MD</code>文件中，引入自定义组件，但需注意该组件必须在<code v-pre>components</code>文件下才生效，当前在<code v-pre>VuepressTest</code>项目中新建<code v-pre>doc/README.md</code>中引入<code v-pre>Test.vue</code>组件，如下所示：</li>
</ol>
<div class="language-tsx ext-tsx line-numbers-mode"><pre v-pre class="language-tsx"><code><span class="token operator">--</span><span class="token operator">-</span>
home<span class="token operator">:</span> <span class="token boolean">true</span>
<span class="token operator">--</span><span class="token operator">-</span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span><span class="token class-name">Test</span></span><span class="token punctuation">></span></span><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span><span class="token class-name">Test</span></span><span class="token punctuation">></span></span>
</code></pre><div class="line-numbers" aria-hidden="true"><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div><div class="line-number"></div></div></div><ol start="2">
<li>效果如下所示：</li>
</ol>
<img src="@source/vue/2021/1222/image007.png" style="zoom:50%;" />
</div></template>


